/**
 * @file soil_adc.c
 * @author your name (you@domain.com)
 * @brief
 * @version 0.1
 * @date 2024-10-17
 *
 * @copyright Copyright (c) 2024
 *
*/
#include "stdlib.h"
#include "stdio.h"
#include "string.h"
#include "bflb_gpio.h"
#include "bflb_adc.h"
#include "FreeRTOS.h"
#include "task.h"
#include "soil_adc.h"

#define DBG_TAG "SOIL-ADC"

struct bflb_device_s* adc;
volatile uint32_t raw_data;

static void adc_isr(int irq, void* arg)
{
    uint32_t intstatus = bflb_adc_get_intstatus(adc);
    if (intstatus & ADC_INTSTS_ADC_READY) {
        bflb_adc_int_clear(adc, ADC_INTCLR_ADC_READY);
        raw_data = bflb_adc_read_raw(adc);
    }
}
soil_adc_callback_t _soil_adc_callback;

static void soil_adc_check(void* arg)
{
    while (1)
    {
        struct bflb_adc_result_s result;
        bflb_adc_start_conversion(adc);
        bflb_adc_parse_result(adc, (uint32_t*)&raw_data, &result, 1);
        // printf("\r\npos chan %d\r\nADC Value = %d\r\nCurrent Voltage = %d mv\r\n", result.pos_chan, result.value, result.millivolt);
        bflb_adc_stop_conversion(adc);
        vTaskDelay(pdMS_TO_TICKS(500));
        if (_soil_adc_callback) {
            _soil_adc_callback(result.millivolt);
        }

    }

}

void soil_adc_init(soil_adc_callback_t soil_adc_callback)
{
    struct bflb_device_s* gpio;

    gpio = bflb_device_get_by_name("gpio");
    bflb_gpio_init(gpio, GPIO_PIN_3, GPIO_ANALOG | GPIO_SMT_EN | GPIO_DRV_0);
    adc = bflb_device_get_by_name("adc");

    struct bflb_adc_config_s cfg;
    cfg.clk_div = ADC_CLK_DIV_32;
    cfg.scan_conv_mode = false;
    cfg.continuous_conv_mode = false;
    cfg.differential_mode = false;
    cfg.resolution = ADC_RESOLUTION_16B;
    cfg.vref = ADC_VREF_3P2V;

    //adc结构体配置

    struct bflb_adc_channel_s chan;

    chan.pos_chan = ADC_CHANNEL_3;
    chan.neg_chan = ADC_CHANNEL_GND;
    //通道配置，单端模式下neg选择GND，pos注意对应IO口的通道

    bflb_adc_init(adc, &cfg);
    bflb_adc_channel_config(adc, &chan, 1);
    bflb_adc_rxint_mask(adc, false);
    bflb_irq_attach(adc->irq_num, adc_isr, NULL);
    bflb_irq_enable(adc->irq_num);
    _soil_adc_callback = soil_adc_callback;
    xTaskCreate(soil_adc_check, "soil_adc_check", 1024*2, NULL, 3, NULL);
}
